package cn.li.security.jwt;

import cn.li.security.json.filter.UsernamePasswordJSONAuthenticationFilter;
import cn.li.security.json.handle.AccessDeniedJSONHandler;
import cn.li.security.json.handle.AuthenticationFailJSONHandler;
import cn.li.security.json.handle.AuthenticationSuccessJSONHandler;
import cn.li.security.json.handle.NoneAuthenticationJSONHandler;
import cn.li.security.jwt.service.IJwtService;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.Setter;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.SecurityConfigurerAdapter;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.web.AuthenticationEntryPoint;
import org.springframework.security.web.DefaultSecurityFilterChain;
import org.springframework.security.web.access.AccessDeniedHandler;
import org.springframework.security.web.authentication.AuthenticationConverter;
import org.springframework.security.web.authentication.AuthenticationSuccessHandler;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;

public class JwtAuthenticationConfiguration extends SecurityConfigurerAdapter<DefaultSecurityFilterChain, HttpSecurity> {

    @Setter
    private AuthenticationConverter authenticationConverter;
    @Setter
    private AuthenticationEntryPoint authenticationEntryPoint;
    @Setter
    private UserDetailsService userDetailsService;

    @Setter
    private IJwtService jwtService;

    public JwtAuthenticationConfiguration(ObjectMapper objectMapper,UserDetailsService userDetailsService,IJwtService jwtService) {
        this.authenticationConverter = new JwtAuthenticationConverter(jwtService);
        this.authenticationEntryPoint= new NoneAuthenticationJSONHandler(objectMapper);
        this.userDetailsService =  userDetailsService;
    }

    @Override
    public void configure(HttpSecurity http) throws Exception {
        JwtAuthenticationFilter filter = new JwtAuthenticationFilter();
        //配置header的解析器
        filter.setAuthenticationConverter(this.authenticationConverter);
        //配置登陆失败的处理器
        filter.setAuthenticationEntryPoint(this.authenticationEntryPoint);
        //取得Manager，然后将Filter添加进去
        filter.setAuthenticationManager(http.getSharedObject(AuthenticationManager.class));
        //配置相对应的Provider
        http    .authenticationProvider(new JwtAuthenticationProvider(this.userDetailsService))
                .addFilterAfter(filter, UsernamePasswordAuthenticationFilter.class)
        ;
    }

}
